﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Drawing;
using System.Drawing.Imaging;
using System.Diagnostics;
using System.Runtime.InteropServices;
using System.IO.MemoryMappedFiles;
using Go;
using GoRpc;

namespace VRTest
{
    class Program
    {
        [DllImport("Kernel32.dll")]
        private static extern void CopyMemory(IntPtr Destination, IntPtr Source, long Length);

        static void Main(string[] args)
        {
            string mname = "VRImage";
            string mpipe = "VRPipe";
            Process labelProcess = new Process();
            labelProcess.StartInfo.FileName = "./VRService.exe";
            labelProcess.StartInfo.Arguments = $"--pipe {mpipe} --mname {mname} --parent {Process.GetCurrentProcess().Id}";
            labelProcess.StartInfo.UseShellExecute = false;
            labelProcess.StartInfo.RedirectStandardOutput = false;
            labelProcess.StartInfo.CreateNoWindow = true;
            if (!labelProcess.Start())
            {
                return;
            }
            work_service work = new work_service();
            work_strand strand = new work_strand(work);
            MemoryMappedFile mmf = MemoryMappedFile.CreateOrOpen(mname, 1 * 1024 * 1024, MemoryMappedFileAccess.ReadWrite);
            MemoryMappedViewAccessor mmv = mmf.CreateViewAccessor(0, 1 * 1024 * 1024);
            IntPtr mmvPtr = socket.get_mmview_ptr(mmv);
            Bitmap bitmap = new Bitmap("../vr.bmp");
            BitmapData data = bitmap.LockBits(new Rectangle(0, 0, bitmap.Width, bitmap.Height), ImageLockMode.ReadOnly, PixelFormat.Format8bppIndexed);
            CopyMemory(mmvPtr, data.Scan0, data.Stride * bitmap.Height);
            generator.go(strand, async delegate ()
            {
                socket_pipe_client pc = new socket_pipe_client(mpipe);
                if (!await pc.connect())
                {
                    return;
                }
                go_rpc.caller caller = new go_rpc.caller(pc);
                caller.run();
                await caller.invoke("MatrixSize", 16);
                await caller.invoke("Symbol", 1);
                await caller.invoke("SymbolType", 4);
                await caller.invoke("BitsPerCell", 4);
                await caller.invoke("SampleWidth", 4);
                await caller.invoke("Prefiletering", false);
                await caller.invoke("ImageWidth", bitmap.Width);
                await caller.invoke("ImageHeight", bitmap.Height);
                tuple<string, short[]> code = await caller.invoke<tuple<string, short[]>>("Read", data.Stride, bitmap.Height);
                Console.WriteLine(code.value1);
                caller.close();
                pc.close();
            });
            work.run();
            Console.ReadKey();
        }
    }
}
